#pragma once
#include "base/core/singleton.h"
#include "Common/MessageDispatch/IMessageDispatch.h"
#include "Common/ServerDefine.h"
#include "ProtoBuffer/ServerInternalProtocol.pb.h"
#include <unordered_map>
#include <list>

using namespace std;
struct MServerZoneInfo;
class MasterMgr : public ManualSingleton<MasterMgr>,
				  public IServerMessageHandler
{
	friend class ManualSingleton<MasterMgr>;

	typedef bool(MasterMgr::*pMsgFunc)(RECV_PACKAGE& package);
	typedef std::unordered_map<int32_t, pMsgFunc> MSGFUNC;

	typedef unordered_map<uint32_t, MServerZoneInfo> ZIDZONEMAP;
	typedef unordered_map<uint32_t, uint32_t>  SESSIONID_MAP;
	typedef unordered_map<uint32_t, uint32_t>  ZONE_STATE_MAP;
	typedef ::google::protobuf::RepeatedField< ::google::protobuf::uint32 > REPEATED_UINT32;
	typedef ::google::protobuf::RepeatedPtrField< ::ProtoBuf::UnOpenZoneInfo >  REPEATED_UNOPEN_ZONES;

	MSGFUNC m_mapMsgFunc; //other servers msg recv func except accountdb

	ZIDZONEMAP m_zones;
	bool      m_bAllZoneOpen;

	REPEATED_UINT32   m_whiteLst;
	REPEATED_UINT32   m_recommZoneIds;
	REPEATED_UNOPEN_ZONES m_unopenZones;

protected:
	//recv from other servers 
	bool RecvPing(RECV_PACKAGE &package);
	bool RegisterFromZone(RECV_PACKAGE &package);
	bool RegisterFromLogin(RECV_PACKAGE &package);

	bool RegisterFromWeb(RECV_PACKAGE &package);

	bool WhiteLstFromWeb(RECV_PACKAGE &package);
	bool ZoneStateReqFromWeb(RECV_PACKAGE& package);
	bool AllZoneOpenFromWeb(RECV_PACKAGE &package);
	bool ZoneOpenFromWeb(RECV_PACKAGE& package);

	//send other servers msg
	bool ZonesInfoToLogin(LoginRegisterRsp&  lRegisterRsp);
	bool NotifyLoginZones();
	bool NotifyLoginWhiteList();
	bool NotifyLoginZoneStates(MServerZoneInfo& zone);
	bool NotifyWebZones();

	bool SendToZoneByZid(const REPEATED_UINT32 &zidLst, uint32_t cmd, const char *data, uint32_t len);

	MServerZoneInfo* GetMasterZoneInfo(uint32_t zid);
public:
	bool Init(bool open);
	bool UnInit();
	bool ClearZoneInfo(uint32_t zid);

	virtual void		onServerMessage(uint32_t actionId, RECV_PACKAGE &package);
	virtual const char* getServerHandlerDebugInfo(void) { return nullptr; };

	MasterMgr();
	~MasterMgr();
};

#define g_MakeMasterMgr() (MasterMgr::Instance())
#define g_GetMasterMgr()  (MasterMgr::GetInstance())
#define g_DelMasterMgr()  (MasterMgr::Destroy())